package com.fmdj.odr.config;

import com.fmdj.odr.db.dao.OrderBillDao;
import com.fmdj.odr.db.dao.OrderDao;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.connection.Message;
import org.springframework.data.redis.connection.MessageListener;
import org.springframework.data.redis.listener.KeyExpirationEventMessageListener;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.serializer.JdkSerializationRedisSerializer;
import org.springframework.stereotype.Component;

import java.util.HashMap;

@Component
@Slf4j
public class KeyExpiredListener extends KeyExpirationEventMessageListener {

    @Autowired
    private OrderDao orderDao;

    @Autowired
    private OrderBillDao orderBillDao;

    //当redis的key过期时，会触发这个监听器
    public KeyExpiredListener(RedisMessageListenerContainer listenerContainer) {
        super(listenerContainer);
    }


    /**
     * 处理 Redis 键过期消息的方法。   整体流程:redis键过期,触发该监听器执行该方法,先判断是否是键过期事件的频道,是的话则处理该事件(先反序列化 取出orderId 再进行数据库的处理)
     *message中包含了键名称和过期时间等信息
     * @param message 消息内容
     * @param pattern 匹配模式
     */
    @Override
    public void onMessage(Message message, byte[] pattern) {
        //检查消息频道是否为键过期事件,只处理该频道事件
        if (new String(message.getChannel()).equals("__keyevent@5__:expired")) {
            //如果是键过期事件，则处理该事件
            //先将key进行反序列化再取出
            JdkSerializationRedisSerializer serializer = new JdkSerializationRedisSerializer();
            String key = serializer.deserialize(message.getBody()).toString(); //获取键名称 order#orderId

            //判断其中是否含有order#这个键
            if (key.contains("order#")) {
                //如果有这个键则获取orderId
                long orderId = Long.parseLong(key.split("#")[1]);

                HashMap<Object, Object> map = new HashMap<>() {{
                    put("orderId", orderId);
                }};
                //删除未结单的订单
                int rows = orderDao.deleteUnAcceptOrder(map);
                if (rows==1) {
                    log.info("成功删除未接单的订单");
                }

                //删除未结单的账单
                rows = orderBillDao.deleteUnAcceptOrderBill(orderId);
                if (rows==1) {
                    log.info("成功删除未接单的账单");
                }
            }
        }
    }
}
